package testsgraphtraversal;

import static org.junit.Assert.*;

import java.util.Iterator;
import java.util.LinkedList;

import graph.AdministratorOfAllStartingNodes;
import graph.BookReviewGraph;
import graph.BookReviewNode;

import org.junit.Before;
import org.junit.Test;

import visitorpattern.VisitorJustPrintsBookReviewNodeInformation;
import bookworm.Review;

public class TestBreadthFirstRandomGraph 
{
	BookReviewGraph graph;
	VisitorJustPrintsBookReviewNodeInformation visitor;
	@Before
	public void setUp()
	{
		/*
		 * the constructed graph is illustrated by a JPEG image in the package "grafosDepthFirstBreadthFirst"
		 * the nodes IDs are in order of visit.
		 */
		
		graph = new BookReviewGraph();
		
		Review review0 = new Review();
		review0.setReviewId(0);
		review0.setReviewTitle("a little creepy~");
		review0.addNewTag("horror");
		Review review1 = new Review();
		review1.addNewTag("horror");
		review1.addNewAuthor("james dashner");
		review1.setReviewId(1);
		review1.setReviewTitle("imagine 'the hunger games' with maze");
		Review review2 = new Review();
		review2.addNewTag("horror");
		review2.addNewTag("romance");
		review2.addNewAuthor("stephenie meyer");
		review2.setReviewId(2);
		review2.setReviewTitle("vampires suck");
		Review review3 = new Review();
		review3.addNewTag("horror");
		review3.addNewTag("romance");
		review3.setReviewId(3);
		review3.setReviewTitle("kinda romantic and disturbing too");
		Review review4 = new Review();
		review4.addNewAuthor("james dashner");
		review4.setReviewId(4);
		review4.setReviewTitle("keeps you wanting to read until last page");
		Review review5 = new Review();
		review5.addNewAuthor("james dashner");
		review5.setReviewId(5);
		review5.setReviewTitle("a-maze-ing!");
		Review review6 = new Review();
		review6.addNewAuthor("stephenie meyer");
		review6.setReviewId(6);
		review6.setReviewTitle("redefining vampire books");
		
		
		BookReviewNode node0 = graph.createNewNode(review0);
		BookReviewNode node1 = graph.createNewNode(review1);
		BookReviewNode node2 = graph.createNewNode(review2);
		BookReviewNode node3 = graph.createNewNode(review3);
		BookReviewNode node4 = graph.createNewNode(review4);
		BookReviewNode node5 = graph.createNewNode(review5);
		BookReviewNode node6 = graph.createNewNode(review6);
		
		//in our graph traversal, we start by starting nodes. Let's set node0 for our only starting node
		AdministratorOfAllStartingNodes setsStartingNodes = AdministratorOfAllStartingNodes.getAdministratorOfAllStartingNodes();
		setsStartingNodes.addNewStartingNodeForTags(node0);
		
		
		graph.createNewEdge(node0, node1);
		graph.createNewEdge(node0, node2);
		graph.createNewEdge(node0, node3);
		graph.createNewEdge(node1, node4);
		graph.createNewEdge(node1, node5);
		graph.createNewEdge(node2, node6);
		graph.createNewEdge(node2, node3);
		
		visitor = new VisitorJustPrintsBookReviewNodeInformation();
		
	}

	@Test
	public void test() 
	{
		/*what's the order we expect the nodes to be visited in the graph? In our test,
		 * it's the same order in which the nodes were inserted in the graph.
		 */
		Iterator<BookReviewNode> expectedGraphVisitOrder = this.graph.getBookReviewNodes();
		LinkedList<BookReviewNode> nodesVisited = graph.breadthFirstTraversal(visitor);
		if(nodesVisited.size() != graph.getNumberOfNodes())
		{
			fail("Breadth first is visiting more/less nodes than it's supposed to visit");
		}
		else
		{
			for(int i = 0; i < nodesVisited.size(); i++)
			{
				BookReviewNode nodeFromExpectedGraphVisitOrder = expectedGraphVisitOrder.next();
				BookReviewNode nodeFromNodesVisitedSequence = nodesVisited.get(i);
				if(nodeFromExpectedGraphVisitOrder.getReviewData().getReviewId() !=  nodeFromNodesVisitedSequence.getReviewData().getReviewId())
				{
					System.out.println(nodeFromExpectedGraphVisitOrder.getReviewData().getReviewId() + "&&" + nodeFromNodesVisitedSequence.getReviewData().getReviewId());
					fail("the order of graph visit using breadth first is wrong");
				}
			}
		}
	}

}
